<script setup lang="ts">
import { ref, reactive, onMounted, onUnmounted, watch } from 'vue'
import FolderList from './components/FolderList.vue'
import NoteList from './components/NoteList.vue'
import NoteEditor from './components/NoteEditor.vue'
import Settings from './components/Settings.vue'
import NotificationContainer from './components/NotificationContainer.vue'
import { saveData, loadData } from './services/storage'
import type { AppData, Folder, Note, SyncResult } from './types'
import {
  initDB,
  saveNotes,
  loadNotes,
  saveFolders,
  loadFolders,
  saveSetting,
  loadSetting,
  getStorageUsage
} from './services/indexedDBStorage'
import { authState } from './services/auth'
import { FolderAPI, NoteAPI, OfflineManager, type Folder as CrudFolder, type Note as CrudNote } from './services/crudApi'
import { showError, showSuccess, showInfo } from './services/notification'
import { formatDateTime } from './utils/dateUtils'

/**
 * 笔记应用的主组件
 * 管理整体布局和状态
 */

// 应用状态
const appState = reactive({
  currentFolder: '全部笔记',
  currentNote: null as Note | null,
  folders: [
    { id: 1, name: '全部笔记', count: 0, isDefault: true, parentId: null },
    { id: 2, name: '未分类笔记', count: 0, isDefault: true, parentId: null }
  ] as Folder[],
  notes: [] as Note[]
})

// UI状态
const showSettings = ref(false)



/**
 * 处理文件夹选择
 * @param folder 选中的文件夹
 */
const handleFolderSelect = (folder: Folder): void => {
  appState.currentFolder = folder.name
  // 清除当前选中的笔记
  appState.currentNote = null

  // 如果选择的是"全部笔记"，不需要过滤
  if (folder.name === '全部笔记') {
    return
  }

  // 如果有笔记且不是"全部笔记"文件夹，选择第一个匹配的笔记
  const folderNotes = appState.notes.filter((note) => {
    if (folder.name === '未分类笔记') {
      // 未分类笔记：folderId为2或者找不到对应文件夹的笔记
      if (note.folderId === 2) {
        return true
      }
      const noteFolder = appState.folders.find((f) => f.id === note.folderId)
      return !noteFolder || noteFolder.isDefault
    } else {
      // 其他文件夹：根据folderId匹配
      return note.folderId === folder.id
    }
  })

  if (folderNotes.length > 0) {
    appState.currentNote = folderNotes[0]
  }
}

/**
 * 处理笔记选择
 * @param note 选中的笔记
 */
const handleNoteSelect = (note: Note): void => {
  appState.currentNote = note
}

/**
 * 创建新笔记
 */
const createNewNote = async (): Promise<void> => {
  const timeString = formatDateTime()

  // 根据当前文件夹确定folderId
  let folderId: number | null = null
  if (appState.currentFolder !== '全部笔记') {
    const currentFolderObj = appState.folders.find((f) => f.name === appState.currentFolder)
    if (currentFolderObj) {
      folderId = currentFolderObj.id
    }
  }

  const noteData = {
    title: '新笔记',
    content: '# 开始写作\n\n在这里记录你的想法...\n\n## 提示\n- 支持 Markdown 语法\n- 可以直接粘贴图片',
    folderId: folderId,
    createdAt: timeString,
    updatedAt: timeString,
    tags: []
  }

  if (authState.isLoggedIn) {
    // 用户已登录，直接调用API创建
    const createdNote = await NoteAPI.create(noteData)
    if (createdNote) {
      appState.notes.unshift(createdNote)
      appState.currentNote = createdNote
      
      // 更新文件夹计数
      updateFolderCounts()
      saveAppData()
      console.log('笔记创建成功:', createdNote.title)
    }
  } else {
    // 用户未登录，保存到本地并标记为待同步
    const localNote = {
      id: Date.now(),
      ...noteData,
      syncStatus: 'pending' as const
    }
    appState.notes.unshift(localNote)
    appState.currentNote = localNote
    OfflineManager.addPendingNote(localNote)
    
    // 更新文件夹计数
    updateFolderCounts()
    saveAppData()
    console.log('笔记已保存到本地，等待同步:', localNote.title)
  }
}

/**
 * 创建新文件夹
 * @param name 文件夹名称
 * @param parentId 父文件夹ID
 * @param isShared 是否为共享文件夹
 */
const createFolder = async (
  name: string,
  parentId: number | null = null,
  isShared: boolean = false
): Promise<void> => {
  const timeString = formatDateTime()
  const folderData = {
    name: name,
    count: 0,
    isDefault: false,
    isShared: isShared,
    parentId: parentId,
    createdAt: timeString,
    updatedAt: timeString
  }

  if (authState.isLoggedIn) {
    // 用户已登录，直接调用API创建
    const createdFolder = await FolderAPI.create(folderData)
    if (createdFolder) {
      appState.folders.push(createdFolder)
      saveAppData()
      console.log('文件夹创建成功:', createdFolder.name)
    }
  } else {
    // 用户未登录，保存到本地并标记为待同步
    const localFolder = {
      id: Date.now(),
      ...folderData,
      syncStatus: 'pending' as const
    }
    appState.folders.push(localFolder)
    OfflineManager.addPendingFolder(localFolder)
    saveAppData()
    console.log('文件夹已保存到本地，等待同步:', localFolder.name)
  }
}

/**
 * 重命名文件夹
 * @param id 文件夹ID
 * @param name 新名称
 */
const renameFolder = async (id: number, name: string): Promise<void> => {
  const folder = appState.folders.find((f) => f.id === id)
  if (folder && !folder.isDefault) {
    const oldName = folder.name
    
    if (authState.isLoggedIn && folder.syncStatus === 'synced') {
      // 用户已登录且文件夹已同步，直接调用API更新
      const updateData = {
        name,
        updatedAt: formatDateTime()
      }
      const updatedFolder = await FolderAPI.update(id, updateData)
      if (updatedFolder) {
        // 更新本地数据
        Object.assign(folder, updatedFolder)
        
        // 如果当前选中的是被重命名的文件夹，更新当前文件夹名称
        if (appState.currentFolder === oldName) {
          appState.currentFolder = name
        }
        
        saveAppData()
        console.log('文件夹重命名成功:', name)
      }
    } else {
      // 用户未登录或文件夹未同步，仅更新本地
      folder.name = name
      folder.updatedAt = formatDateTime()
      
      // 如果当前选中的是被重命名的文件夹，更新当前文件夹名称
      if (appState.currentFolder === oldName) {
        appState.currentFolder = name
      }
      
      saveAppData()
      console.log('文件夹已在本地重命名:', name)
    }
  }
}

/**
 * 删除文件夹
 * @param id 文件夹ID
 */
const deleteFolder = async (id: number): Promise<void> => {
  const folderIndex = appState.folders.findIndex((f) => f.id === id)
  if (folderIndex > -1) {
    const folder = appState.folders[folderIndex]

    // 检查是否为默认文件夹，如果是则不允许删除
    if (folder.isDefault) {
      return
    }

    if (authState.isLoggedIn && folder.syncStatus === 'synced') {
      // 用户已登录且文件夹已同步，调用API删除
      const success = await FolderAPI.delete(id)
      if (success) {
        // 删除该文件夹下的所有笔记
        appState.notes = appState.notes.filter((note) => note.folderId !== id)

        // 删除文件夹
        appState.folders.splice(folderIndex, 1)

        // 如果当前选中的是被删除的文件夹，切换到全部笔记
        if (appState.currentFolder === folder.name) {
          appState.currentFolder = '全部笔记'
          appState.currentNote = null
        }
        
        saveAppData()
        console.log('文件夹删除成功:', folder.name)
      }
    } else {
      // 用户未登录或文件夹未同步，仅删除本地
      // 删除该文件夹下的所有笔记
      appState.notes = appState.notes.filter((note) => note.folderId !== id)

      // 删除文件夹
      appState.folders.splice(folderIndex, 1)

      // 如果当前选中的是被删除的文件夹，切换到全部笔记
      if (appState.currentFolder === folder.name) {
        appState.currentFolder = '全部笔记'
        appState.currentNote = null
      }
      
      saveAppData()
      console.log('文件夹已在本地删除:', folder.name)
    }
  }
}

/**
 * 移动文件夹
 * @param folderId 要移动的文件夹ID
 * @param targetFolderId 目标父文件夹ID
 */
const moveFolder = (folderId: number, targetFolderId: number): void => {
  const folder = appState.folders.find((f) => f.id === folderId)
  const targetFolder = appState.folders.find((f) => f.id === targetFolderId)

  if (folder && targetFolder && !folder.isDefault) {
    // 检查是否会造成循环引用
    let currentParent: Folder | null = targetFolder
    while (currentParent && currentParent.parentId) {
      if (currentParent.parentId === folderId) {
        // 会造成循环引用，不允许移动
        return
      }
      currentParent = appState.folders.find((f) => f.id === currentParent!.parentId!) || null
    }

    // 更新父文件夹ID和时间戳
    folder.parentId = targetFolderId
    folder.updatedAt = formatDateTime()
    folder.syncStatus = 'modified' // 标记为已修改，同步时保持本地更改
    
    // 添加待同步更改
    if (authState.isLoggedIn) {
      addPendingChange({
        type: 'folder',
        action: 'update',
        data: { ...folder }
      })
    }
  }
}

/**
 * 重新排序文件夹
 * @param draggedFolderId 被拖拽的文件夹ID
 * @param targetFolderId 目标文件夹ID
 * @param position 插入位置（'before' 或 'after'）
 */
const reorderFolders = async (draggedFolderId: number, targetFolderId: number, position: 'before' | 'after'): Promise<void> => {
  console.log('=== 开始文件夹排序 ===')
  console.log('拖拽文件夹ID:', draggedFolderId, '目标文件夹ID:', targetFolderId, '位置:', position)
  
  const draggedFolder = appState.folders.find(f => f.id === draggedFolderId)
  const targetFolder = appState.folders.find(f => f.id === targetFolderId)
  
  console.log('拖拽文件夹:', draggedFolder?.name, '目标文件夹:', targetFolder?.name)
  
  if (!draggedFolder || !targetFolder) {
    console.error('找不到要排序的文件夹')
    return
  }
  
  // 检查是否是默认文件夹
  if (draggedFolder.isDefault || targetFolder.isDefault) {
    console.error('默认文件夹不能参与排序')
    return
  }
  
  // 确保两个文件夹在同一层级
  if (draggedFolder.parentId !== targetFolder.parentId) {
    console.error('只能在同一层级内排序文件夹')
    return
  }
  
  // 获取同层级的所有文件夹（包括默认文件夹，因为它们也可能需要排序）
  const siblingFolders = appState.folders
    .filter(f => f.parentId === draggedFolder.parentId)
    .sort((a, b) => {
      // 默认文件夹排在前面
      if (a.isDefault && !b.isDefault) return -1
      if (!a.isDefault && b.isDefault) return 1
      // 同类型文件夹按sortOrder排序
      return (a.sortOrder || 0) - (b.sortOrder || 0)
    })
  
  // 移除被拖拽的文件夹
  const filteredSiblings = siblingFolders.filter(f => f.id !== draggedFolderId)
  
  // 找到目标位置
  const targetIndex = filteredSiblings.findIndex(f => f.id === targetFolderId)
  const insertIndex = position === 'before' ? targetIndex : targetIndex + 1
  
  // 插入被拖拽的文件夹
  filteredSiblings.splice(insertIndex, 0, draggedFolder)
  
  // 重新分配排序号
  filteredSiblings.forEach((folder, index) => {
    folder.sortOrder = index + 1
    folder.updatedAt = formatDateTime()
  })
  
  // 将排序更改应用到appState.folders中
  filteredSiblings.forEach(updatedFolder => {
    const folderIndex = appState.folders.findIndex(f => f.id === updatedFolder.id)
    if (folderIndex !== -1) {
      appState.folders[folderIndex] = { ...appState.folders[folderIndex], ...updatedFolder }
    }
  })
  
  // 保存到本地存储
  await saveAppData()
  
  // 如果用户已登录，调用API更新排序
  if (authState.isLoggedIn) {
    try {
      // 准备批量更新数据
      const updateData = filteredSiblings
        .filter(folder => folder.syncStatus === 'synced')
        .map(folder => ({
          id: folder.id,
          sortOrder: folder.sortOrder
        }))
      
      if (updateData.length > 0) {
        const success = await FolderAPI.batchUpdateOrder(updateData)
        if (success) {
          console.log('文件夹排序已批量同步到服务器')
        } else {
          // 批量更新失败，标记为待同步
          filteredSiblings.forEach(folder => {
            if (folder.syncStatus === 'synced') {
              folder.syncStatus = 'pending'
            }
          })
        }
      }
    } catch (error) {
      console.error('同步文件夹排序失败:', error)
      // 标记为待同步
      filteredSiblings.forEach(folder => {
        if (folder.syncStatus === 'synced') {
          folder.syncStatus = 'pending'
        }
      })
    }
  } else {
    // 未登录时标记为待同步
    filteredSiblings.forEach(folder => {
      folder.syncStatus = 'pending'
    })
  }
  
  console.log(`文件夹 "${draggedFolder.name}" 已移动到 "${targetFolder.name}" ${position === 'before' ? '之前' : '之后'}`)
}

/**
 * 更新文件夹信息
 * @param updatedFolder 更新后的文件夹对象
 */
const updateFolder = (updatedFolder: Folder): void => {
  const folderIndex = appState.folders.findIndex((f) => f.id === updatedFolder.id)
  if (folderIndex > -1) {
    // 更新文件夹信息
    appState.folders[folderIndex] = { ...appState.folders[folderIndex], ...updatedFolder }
    
    // 添加待同步更改
    if (authState.isLoggedIn) {
      addPendingChange({
        type: 'folder',
        action: 'update',
        data: { ...updatedFolder }
      })
    }
    
    console.log(`文件夹 "${updatedFolder.name}" 已更新，共享状态: ${updatedFolder.isShared ? '是' : '否'}`)
  }
}

/**
 * 移动笔记到指定文件夹
 * @param noteId 笔记ID
 * @param targetFolderId 目标文件夹ID，null表示移动到未分类笔记
 */
const moveNoteToFolder = (noteId: number, targetFolderId: number | null): void => {
  const note = appState.notes.find((n) => n.id === noteId)
  
  if (note) {
    if (targetFolderId === null) {
      // 移动到未分类笔记
      note.folderId = 2 // 未分类笔记的ID是2
      console.log(`笔记 "${note.title}" 已移动到未分类笔记`)
    } else {
      const targetFolder = appState.folders.find((f) => f.id === targetFolderId)
      if (targetFolder) {
        note.folderId = targetFolderId
        console.log(`笔记 "${note.title}" 已移动到文件夹 "${targetFolder.name}"`)
      }
    }
    
    // 更新笔记的修改时间和同步状态
    note.updatedAt = formatDateTime()
    note.syncStatus = 'modified' // 标记为已修改，同步时保持本地更改
    
    // 更新文件夹计数
    updateFolderCounts()
    
    // 添加待同步更改
    if (authState.isLoggedIn) {
      addPendingChange({
        type: 'note',
        action: 'update',
        data: { ...note }
      })
    }
  }
}

/**
 * 重命名笔记
 * @param id 笔记ID
 * @param title 新标题
 */
const renameNote = async (id: number, title: string): Promise<void> => {
  const note = appState.notes.find((n) => n.id === id)
  if (note) {
    if (authState.isLoggedIn && note.syncStatus === 'synced') {
      // 用户已登录且笔记已同步，调用API更新
      const updateData = {
        title,
        updatedAt: formatDateTime()
      }
      const updatedNote = await NoteAPI.update(id, updateData)
      if (updatedNote) {
        // 更新本地数据
        Object.assign(note, updatedNote)
        
        // 如果当前选中的是被重命名的笔记，更新当前笔记
        if (appState.currentNote?.id === id) {
          Object.assign(appState.currentNote, updatedNote)
        }
        
        saveAppData()
        console.log('笔记重命名成功:', title)
      }
    } else {
      // 用户未登录或笔记未同步，仅更新本地
      note.title = title
      note.updatedAt = formatDateTime()
      note.syncStatus = 'pending'
      
      // 如果当前选中的是被重命名的笔记，更新当前笔记
      if (appState.currentNote?.id === id) {
        appState.currentNote.title = title
        appState.currentNote.updatedAt = note.updatedAt
      }
      
      saveAppData()
      console.log('笔记已在本地重命名:', title)
    }
  }
}

/**
 * 删除笔记
 * @param id 笔记ID
 */
const deleteNote = async (id: number): Promise<void> => {
  const noteIndex = appState.notes.findIndex((n) => n.id === id)
  if (noteIndex > -1) {
    const note = appState.notes[noteIndex]
    
    if (authState.isLoggedIn && note.syncStatus === 'synced') {
      // 用户已登录且笔记已同步，调用API删除
      const success = await NoteAPI.delete(id)
      if (success) {
        // 删除本地笔记
        appState.notes.splice(noteIndex, 1)

        // 如果当前选中的是被删除的笔记，清空当前笔记
        if (appState.currentNote?.id === id) {
          appState.currentNote = null
        }

        // 更新文件夹计数
        updateFolderCounts()
        saveAppData()
        console.log('笔记删除成功:', note.title)
      }
    } else {
      // 用户未登录或笔记未同步，仅删除本地
      // 删除笔记
      appState.notes.splice(noteIndex, 1)

      // 如果当前选中的是被删除的笔记，清空当前笔记
      if (appState.currentNote?.id === id) {
        appState.currentNote = null
      }

      // 更新文件夹计数
      updateFolderCounts()
      saveAppData()
      console.log('笔记已在本地删除:', note.title)
    }
  }
}

/**
 * 更新文件夹笔记计数
 */
const updateFolderCounts = (): void => {
  appState.folders.forEach((folder) => {
    if (folder.name === '全部笔记') {
      // 全部笔记显示所有笔记的数量
      folder.count = appState.notes.length
    } else if (folder.name === '未分类笔记') {
      // 未分类笔记显示folderId为2或者找不到对应文件夹的笔记
      folder.count = appState.notes.filter((note) => {
        // folderId为2的笔记，或者folderId对应的文件夹不存在或是默认文件夹的笔记
        if (note.folderId === 2) {
          return true
        }
        const noteFolder = appState.folders.find((f) => f.id === note.folderId)
        return !noteFolder || noteFolder.isDefault
      }).length
    } else {
      // 其他文件夹按ID匹配
      folder.count = appState.notes.filter((note) => note.folderId === folder.id).length
    }
  })
}

/**
 * 保存应用数据到IndexedDB
 */
const saveAppData = async (): Promise<void> => {
  try {
    // 将响应式对象转换为普通对象，避免DataCloneError
    const plainNotes = JSON.parse(JSON.stringify(appState.notes))
    const plainFolders = JSON.parse(JSON.stringify(appState.folders))
    const plainCurrentFolder = JSON.parse(JSON.stringify(appState.currentFolder))
    const plainCurrentNoteId = appState.currentNote
      ? JSON.parse(JSON.stringify(appState.currentNote.id))
      : null

    await Promise.all([
      saveNotes(plainNotes),
      saveFolders(plainFolders),
      saveSetting('currentFolder', plainCurrentFolder),
      saveSetting('currentNoteId', plainCurrentNoteId)
    ])
    console.log('应用数据已保存到IndexedDB')
  } catch (error) {
    console.error('保存数据失败:', error)
    console.error('错误详情:', {
      errorName: error instanceof Error ? error.name : 'Unknown',
      errorMessage: error instanceof Error ? error.message : String(error),
      errorStack: error instanceof Error ? error.stack : undefined
    })

    // 降级到localStorage
    try {
      const data: AppData = {
        folders: JSON.parse(JSON.stringify(appState.folders)),
        notes: JSON.parse(JSON.stringify(appState.notes)),
        currentFolder: appState.currentFolder,
        currentNoteId: appState.currentNote?.id || null
      }
      saveData(data)
      console.log('已降级到localStorage保存')
    } catch (fallbackError) {
      console.error('localStorage保存也失败:', fallbackError)
    }
  }
}

/**
 * 合并本地和服务器文件夹数据
 * @param localFolders 本地文件夹数据
 * @param serverFolders 服务器文件夹数据
 * @returns 合并后的文件夹数据
 */
const mergeLocalAndServerFolders = (localFolders: Folder[], serverFolders: Folder[]): Folder[] => {
  const merged = [...localFolders]
  
  for (const serverFolder of serverFolders) {
    // 查找本地是否存在相同ID或相同名称的文件夹
    let localIndex = merged.findIndex(f => f.id === serverFolder.id)
    
    if (localIndex === -1) {
      // 按名称查找（避免重复）
      localIndex = merged.findIndex(f => 
        f.name === serverFolder.name && 
        f.isDefault === serverFolder.isDefault &&
        f.isShared === serverFolder.isShared
      )
    }
    
    if (localIndex >= 0) {
      const localFolder = merged[localIndex]
      
      // 检查本地是否有未同步的更改
      const hasLocalChanges = localFolder.syncStatus === 'pending' || localFolder.syncStatus === 'modified'
      
      if (!hasLocalChanges) {
        // 没有本地更改，使用服务器数据更新
        merged[localIndex] = {
          ...serverFolder,
          id: localFolder.id, // 保持本地ID
          syncStatus: 'synced'
        }
        console.log(`更新文件夹: ${serverFolder.name}`)
      } else {
        console.log(`保持本地文件夹更改: ${localFolder.name}`)
      }
    } else {
      // 服务器有新文件夹，添加到本地
      merged.push({
        ...serverFolder,
        syncStatus: 'synced'
      })
      console.log(`添加服务器文件夹: ${serverFolder.name}`)
    }
  }
  
  return merged
}

/**
 * 合并本地和服务器笔记数据
 * @param localNotes 本地笔记数据
 * @param serverNotes 服务器笔记数据
 * @returns 合并后的笔记数据
 */
const mergeLocalAndServerNotes = (localNotes: Note[], serverNotes: Note[]): Note[] => {
  const merged = [...localNotes]
  
  for (const serverNote of serverNotes) {
    // 查找本地是否存在相同ID的笔记
    let localIndex = merged.findIndex(n => n.id === serverNote.id)
    
    if (localIndex === -1) {
      // 按标题和内容查找（避免重复）
      localIndex = merged.findIndex(n => 
        n.title === serverNote.title && 
        n.content === serverNote.content
      )
    }
    
    if (localIndex >= 0) {
      const localNote = merged[localIndex]
      
      // 检查本地是否有未同步的更改
      const hasLocalChanges = localNote.syncStatus === 'pending' || localNote.syncStatus === 'modified'
      
      if (!hasLocalChanges) {
        // 没有本地更改，使用服务器数据更新
        merged[localIndex] = {
          ...serverNote,
          id: localNote.id, // 保持本地ID
          syncStatus: 'synced'
        }
        console.log(`更新笔记: ${serverNote.title}`)
      } else {
        console.log(`保持本地笔记更改: ${localNote.title}`)
      }
    } else {
      // 服务器有新笔记，添加到本地
      merged.push({
        ...serverNote,
        syncStatus: 'synced'
      })
      console.log(`添加服务器笔记: ${serverNote.title}`)
    }
  }
  
  return merged
}

/**
 * 清理不需要的文件夹
 */
const cleanupUnwantedFolders = (): void => {
  // 移除"我的共享"文件夹，但保留用户创建的待同步数据
  const unwantedFolders = ['我的共享']
  
  unwantedFolders.forEach(folderName => {
    const folderIndex = appState.folders.findIndex(f => 
      f.name === folderName && 
      f.syncStatus !== 'pending' // 不删除待同步的用户数据
    )
    if (folderIndex !== -1) {
      appState.folders.splice(folderIndex, 1)
      console.log(`清理不需要的文件夹: ${folderName}`)
    }
  })
  
  // 移除任何标记为共享但名称包含"共享"的默认文件夹，但保留用户创建的待同步数据
  const sharedDefaultFolders = appState.folders.filter(f => 
    f.isShared && 
    (f.name.includes('共享') || f.name.includes('shared')) && 
    !f.parentId && // 只处理根级文件夹
    f.syncStatus !== 'pending' // 不删除待同步的用户数据
  )
  
  sharedDefaultFolders.forEach(folder => {
    const folderIndex = appState.folders.findIndex(f => f.id === folder.id)
    if (folderIndex !== -1) {
      appState.folders.splice(folderIndex, 1)
      console.log(`清理共享默认文件夹: ${folder.name}`)
    }
  })
}

/**
 * 确保默认文件夹存在
 */
const ensureDefaultFolders = (): void => {
  
  const defaultFolders = [
    { id: 1, name: '全部笔记', count: 0, isDefault: true, parentId: null },
    { id: 2, name: '未分类笔记', count: 0, isDefault: true, parentId: null }
  ]

  defaultFolders.forEach((defaultFolder) => {
    // 检查是否存在具有相同名称和相同属性的文件夹
    const exists = appState.folders.find((f) => 
      f.name === defaultFolder.name && 
      (defaultFolder.isDefault ? f.isDefault : f.isShared)
    )
    
    if (!exists) {
      // 检查是否有同名但属性不同的文件夹，如果有则更新其属性
      const sameNameFolder = appState.folders.find((f) => f.name === defaultFolder.name)
      if (sameNameFolder) {
        // 更新现有文件夹的属性
        if (defaultFolder.isDefault) {
          sameNameFolder.isDefault = true
        }
        if (defaultFolder.isShared) {
          sameNameFolder.isShared = true
        }
        console.log(`更新文件夹属性: ${defaultFolder.name}`)
      } else {
        // 添加新的默认文件夹
        appState.folders.unshift(defaultFolder)
        console.log(`添加默认文件夹: ${defaultFolder.name}`)
      }
    }
  })
  
  // 移除重复的默认文件夹，但保留用户创建的待同步数据
  const seenNames = new Set()
  appState.folders = appState.folders.filter((folder) => {
    const key = `${folder.name}_${folder.isDefault ? 'default' : ''}_${folder.isShared ? 'shared' : ''}`
    if (seenNames.has(key)) {
      // 如果是待同步的用户数据，保留它
      if (folder.syncStatus === 'pending') {
        console.log(`保留待同步的重复文件夹: ${folder.name}`)
        return true
      }
      console.log(`移除重复文件夹: ${folder.name}`)
      return false
    }
    seenNames.add(key)
    return true
  })
}

/**
 * 从IndexedDB加载应用数据
 */
const loadAppData = async (): Promise<void> => {
  try {
    await initDB()

    const [notes, folders, currentFolder, currentNoteId] = await Promise.all([
      loadNotes(),
      loadFolders(),
      loadSetting('currentFolder'),
      loadSetting('currentNoteId')
    ])

    // 如果IndexedDB中没有数据，尝试从localStorage迁移
    if (notes.length === 0 && folders.length === 0) {
      console.log('IndexedDB中无数据，尝试从localStorage迁移')
      const legacyData = loadData()
      appState.folders = legacyData.folders
      appState.notes = legacyData.notes
      appState.currentFolder = legacyData.currentFolder

      if (legacyData.currentNoteId) {
        appState.currentNote =
          appState.notes.find((note) => note.id === legacyData.currentNoteId) || null
      }

      // 立即清理不需要的文件夹，防止闪现
      cleanupUnwantedFolders()
      
      // 确保默认文件夹存在
      ensureDefaultFolders()

      // 保存到IndexedDB
      await saveAppData()
    } else {
      appState.folders = folders
      appState.notes = notes
      appState.currentFolder = currentFolder || '全部笔记'

      if (currentNoteId) {
        appState.currentNote = appState.notes.find((note) => note.id === currentNoteId) || null
      }

      // 立即清理不需要的文件夹，防止闪现
      cleanupUnwantedFolders()
      
      // 确保默认文件夹存在
      ensureDefaultFolders()
    }

    updateFolderCounts()
    console.log('应用数据加载完成')
  } catch (error) {
    console.error('从IndexedDB加载数据失败，降级到localStorage:', error)
    const data = loadData()
    appState.folders = data.folders
    appState.notes = data.notes
    appState.currentFolder = data.currentFolder

    if (data.currentNoteId) {
      appState.currentNote = appState.notes.find((note) => note.id === data.currentNoteId) || null
    }

    // 立即清理不需要的文件夹，防止闪现
    cleanupUnwantedFolders()
    
    // 确保默认文件夹存在
    ensureDefaultFolders()
    updateFolderCounts()
  }
}

// 同步状态管理
const syncState = reactive({
  isOnlineDataSyncing: false,
  syncProgress: 0,
  syncMessage: '',
  autoRetryTimer: null as NodeJS.Timeout | null,
  retryCount: 0,
  maxRetries: 3
})

/**
 * 处理离线数据同步
 */
const handleOfflineDataSync = async (): Promise<SyncResult | null> => {
  if (!authState.isLoggedIn) {
    console.log('用户未登录，跳过离线数据同步')
    return null
  }

  try {
    syncState.isOnlineDataSyncing = true
    syncState.syncProgress = 0
    syncState.syncMessage = '正在检查待同步数据...'

    // 获取待同步的数据
    const pendingFolders = appState.folders.filter(f => f.syncStatus === 'pending' || f.syncStatus === 'modified')
    const pendingNotes = appState.notes.filter(n => n.syncStatus === 'pending' || n.syncStatus === 'modified')

    const totalItems = pendingFolders.length + pendingNotes.length

    if (totalItems === 0) {
      console.log('没有待同步的数据')
      syncState.isOnlineDataSyncing = false
      return { success: true, failedCount: 0, totalCount: 0 }
    }

    console.log(`发现 ${totalItems} 项待同步数据：${pendingFolders.length} 个文件夹，${pendingNotes.length} 个笔记`)
    showInfo(`发现 ${totalItems} 项待同步数据，开始同步...`, '数据同步')

    let syncedItems = 0

    // 同步文件夹
    for (const folder of pendingFolders) {
      try {
        syncState.syncMessage = `正在同步文件夹: ${folder.name}`
        
        if (folder.syncStatus === 'pending') {
          // 创建新文件夹
          const createdFolder = await FolderAPI.create({
            name: folder.name,
            count: folder.count,
            isDefault: folder.isDefault,
            isShared: folder.isShared || false,
            parentId: folder.parentId,
            createdAt: folder.createdAt,
            updatedAt: folder.updatedAt
          })
          
          if (createdFolder) {
            // 更新本地文件夹ID和状态
            const oldId = folder.id
            Object.assign(folder, createdFolder, { syncStatus: 'synced' })
            
            // 更新引用该文件夹的笔记
            appState.notes.forEach(note => {
              if (note.folderId === oldId) {
                note.folderId = createdFolder.id
              }
            })
            
            console.log(`文件夹同步成功: ${folder.name}`)
          }
        } else if (folder.syncStatus === 'modified') {
          // 更新现有文件夹
          const updatedFolder = await FolderAPI.update(folder.id, {
            name: folder.name,
            isShared: folder.isShared,
            parentId: folder.parentId,
            updatedAt: folder.updatedAt
          })
          
          if (updatedFolder) {
            Object.assign(folder, updatedFolder, { syncStatus: 'synced' })
            console.log(`文件夹更新成功: ${folder.name}`)
          }
        }
        
        syncedItems++
        syncState.syncProgress = Math.round((syncedItems / totalItems) * 100)
      } catch (error) {
        console.error(`同步文件夹失败: ${folder.name}`, error)
        // 继续同步其他项目
      }
    }

    // 同步笔记
    for (const note of pendingNotes) {
      try {
        syncState.syncMessage = `正在同步笔记: ${note.title}`
        
        if (note.syncStatus === 'pending') {
          // 创建新笔记
          const createdNote = await NoteAPI.create({
            title: note.title,
            content: note.content,
            folderId: note.folderId,
            createdAt: note.createdAt,
            updatedAt: note.updatedAt,
            tags: note.tags || []
          })
          
          if (createdNote) {
            Object.assign(note, createdNote, { syncStatus: 'synced' })
            console.log(`笔记同步成功: ${note.title}`)
          }
        } else if (note.syncStatus === 'modified') {
          // 更新现有笔记
          const updatedNote = await NoteAPI.update(note.id, {
            title: note.title,
            content: note.content,
            folderId: note.folderId,
            updatedAt: note.updatedAt,
            tags: note.tags
          })
          
          if (updatedNote) {
            Object.assign(note, updatedNote, { syncStatus: 'synced' })
            console.log(`笔记更新成功: ${note.title}`)
          }
        }
        
        syncedItems++
        syncState.syncProgress = Math.round((syncedItems / totalItems) * 100)
      } catch (error) {
        console.error(`同步笔记失败: ${note.title}`, error)
        // 继续同步其他项目
      }
    }

    // 保存同步后的数据
    await saveAppData()
    
    syncState.syncMessage = '同步完成'
    syncState.syncProgress = 100
    
    showSuccess(`成功同步 ${syncedItems} 项数据`, '同步完成')
    console.log(`离线数据同步完成，共同步 ${syncedItems}/${totalItems} 项`)
    
    const failedCount = totalItems - syncedItems
    const result = {
      success: failedCount === 0,
      failedCount,
      totalCount: totalItems
    }
    
    // 如果完全同步成功，停止自动重试
    if (result.success) {
      stopAutoRetrySync()
    }
    
    return result
    
  } catch (error) {
    console.error('离线数据同步失败:', error)
    showError('离线数据同步失败，请稍后重试', '同步错误')
    return null
  } finally {
    syncState.isOnlineDataSyncing = false
    syncState.syncProgress = 0
    syncState.syncMessage = ''
  }
}

// 组件挂载时加载数据
onMounted(async () => {
  await loadAppData()
  
  // 如果用户已登录，加载服务器数据并同步离线数据
  if (authState.isLoggedIn) {
    await loadServerData()
    await handleOfflineDataSync()
  }
  
  // 监听token过期事件
  window.addEventListener('auth:expired', handleAuthExpired)
  
  // 监听用户登录事件
  window.addEventListener('user:login', handleUserLogin)
  
  // 监听启动自动重试事件
  window.addEventListener('sync:start-auto-retry', handleStartAutoRetry)
  
  console.log('应用已启动')
})

/**
 * 加载服务器数据
 */
const loadServerData = async (): Promise<void> => {
  try {
    console.log('开始加载服务器数据...')
    
    // 并行加载文件夹和笔记
    const [serverFolders, serverNotes] = await Promise.all([
      FolderAPI.getAll(),
      NoteAPI.getAll()
    ])
    
    // 智能合并服务器数据到本地，保留待同步的数据
    mergeServerDataWithLocal(serverFolders, serverNotes)
    
    // 确保默认文件夹存在
    ensureDefaultFolders()
    
    // 更新文件夹计数
    updateFolderCounts()
    
    // 保存到本地
    await saveAppData()
    
    console.log('服务器数据加载完成')
  } catch (error) {
    console.error('加载服务器数据失败:', error)
  }
}

/**
 * 智能合并服务器数据与本地数据
 * @param serverFolders 服务器文件夹数据
 * @param serverNotes 服务器笔记数据
 */
const mergeServerDataWithLocal = (serverFolders: any[], serverNotes: any[]): void => {
  // 保留本地待同步的文件夹
  const localPendingFolders = appState.folders.filter(f => f.syncStatus === 'pending')
  
  // 保留本地待同步的笔记
  const localPendingNotes = appState.notes.filter(n => n.syncStatus === 'pending')
  
  // 合并文件夹：服务器数据 + 本地待同步数据
  const mergedFolders = [...serverFolders]
  localPendingFolders.forEach(localFolder => {
    // 检查服务器是否已有同名文件夹
    const existsOnServer = serverFolders.find(sf => sf.name === localFolder.name)
    if (!existsOnServer) {
      mergedFolders.push(localFolder)
      console.log(`保留待同步文件夹: ${localFolder.name}`)
    }
  })
  
  // 合并笔记：服务器数据 + 本地待同步数据
  const mergedNotes = [...serverNotes]
  localPendingNotes.forEach(localNote => {
    // 检查服务器是否已有同标题笔记
    const existsOnServer = serverNotes.find(sn => sn.title === localNote.title && sn.folderId === localNote.folderId)
    if (!existsOnServer) {
      mergedNotes.push(localNote)
      console.log(`保留待同步笔记: ${localNote.title}`)
    }
  })
  
  // 更新应用状态
  appState.folders = mergedFolders
  appState.notes = mergedNotes
  
  console.log(`数据合并完成: ${serverFolders.length} 个服务器文件夹 + ${localPendingFolders.length} 个待同步文件夹`)
  console.log(`数据合并完成: ${serverNotes.length} 个服务器笔记 + ${localPendingNotes.length} 个待同步笔记`)
}

/**
 * 启动自动重试同步
 */
const startAutoRetrySync = (): void => {
  // 清除之前的定时器
  if (syncState.autoRetryTimer) {
    clearTimeout(syncState.autoRetryTimer)
  }
  
  // 检查是否超过最大重试次数
  if (syncState.retryCount >= syncState.maxRetries) {
    console.log('已达到最大重试次数，停止自动重试')
    showError('数据同步多次失败，请检查网络连接或稍后手动重试', '同步失败')
    return
  }
  
  // 计算重试延迟时间（递增延迟：30秒、60秒、120秒）
  const retryDelay = Math.min(30000 * Math.pow(2, syncState.retryCount), 120000)
  
  console.log(`将在 ${retryDelay / 1000} 秒后进行第 ${syncState.retryCount + 1} 次重试`)
  
  syncState.autoRetryTimer = setTimeout(async () => {
    syncState.retryCount++
    console.log(`开始第 ${syncState.retryCount} 次自动重试同步`)
    
    try {
      const syncResult = await handleOfflineDataSync()
      
      if (syncResult && syncResult.totalCount > 0) {
        if (syncResult.success) {
          showSuccess(`重试成功！已同步 ${syncResult.totalCount} 项数据到云端`, '同步完成')
          // 重置重试计数
          syncState.retryCount = 0
        } else {
          showInfo(`第 ${syncState.retryCount} 次重试：${syncResult.failedCount}/${syncResult.totalCount} 项数据仍然失败`, '重试中')
          // 继续重试
          startAutoRetrySync()
        }
      } else {
        // 没有待同步数据，重置重试计数
        syncState.retryCount = 0
      }
    } catch (error) {
      console.error(`第 ${syncState.retryCount} 次重试失败:`, error)
      // 继续重试
      startAutoRetrySync()
    }
  }, retryDelay)
}

/**
 * 停止自动重试同步
 */
const stopAutoRetrySync = (): void => {
  if (syncState.autoRetryTimer) {
    clearTimeout(syncState.autoRetryTimer)
    syncState.autoRetryTimer = null
  }
  syncState.retryCount = 0
}

/**
 * 处理启动自动重试事件
 */
const handleStartAutoRetry = (event: CustomEvent): void => {
  console.log('收到启动自动重试事件:', event.detail)
  startAutoRetrySync()
}

/**
 * 处理用户登录事件
 */
const handleUserLogin = async (event: CustomEvent): Promise<void> => {
  console.log('收到用户登录事件，开始数据获取和同步')
  
  try {
    // 1. 先获取服务器数据并智能合并（保留待同步数据）
    console.log('开始获取服务器数据...')
    await loadServerData()
    
    // 2. 立即同步本地待同步数据到云端
    console.log('开始自动同步本地数据到云端...')
    const syncResult = await handleOfflineDataSync()
    
    // 3. 根据同步结果显示不同的提示并启动自动重试
    if (syncResult && syncResult.totalCount > 0) {
      if (syncResult.success) {
        showSuccess(`登录成功！已同步 ${syncResult.totalCount} 项数据到云端`, '同步完成')
        // 重置重试计数
        syncState.retryCount = 0
      } else {
        showInfo(`登录成功！${syncResult.failedCount}/${syncResult.totalCount} 项数据同步失败，将自动重试`, '部分同步完成')
        // 启动自动重试
        startAutoRetrySync()
      }
    } else {
      showSuccess('登录成功，数据已同步！', '登录完成')
      // 重置重试计数
      syncState.retryCount = 0
    }
    
    console.log('用户登录后的数据获取和同步操作完成')
    
  } catch (error) {
    console.error('登录后数据同步失败:', error)
    showError('登录成功，但数据同步失败，请稍后手动刷新', '同步错误')
  }
}

/**
 * 处理token过期事件
 */
const handleAuthExpired = (event: CustomEvent): void => {
  console.log('收到token过期事件，准备显示登录界面')
  
  // 显示通知
  showError(event.detail?.message || '登录已过期，请重新登录', 'Token过期', 0)
  
  // 触发显示登录框的事件
  // 由于FolderList组件管理登录状态，我们通过DOM事件来通知它显示登录框
  setTimeout(() => {
    window.dispatchEvent(new CustomEvent('show:login', {
      detail: { reason: 'token_expired' }
    }))
  }, 500) // 延迟500ms确保错误通知先显示
}

// 组件卸载时清理
onUnmounted(() => {
  // 移除事件监听器
  window.removeEventListener('auth:expired', handleAuthExpired)
  window.removeEventListener('user:login', handleUserLogin)
  window.removeEventListener('sync:start-auto-retry', handleStartAutoRetry)
  
  // 清理云端保存定时器
  if (cloudSaveTimer) {
    clearTimeout(cloudSaveTimer)
    cloudSaveTimer = null
  }
  
  // 清理自动重试定时器
  stopAutoRetrySync()
  
  console.log('应用组件已卸载')
})

// 云端保存定时器
let cloudSaveTimer: ReturnType<typeof setTimeout> | null = null

/**
 * 处理笔记更新
 * @param updatedNote 更新的笔记数据
 */
const handleNoteUpdate = async (updatedNote: Partial<Note>): Promise<void> => {
  if (!appState.currentNote) return

  // 准备更新数据，包含updatedAt
  const updateData = {
    ...updatedNote,
    updatedAt: formatDateTime()
  }

  // 立即更新本地笔记内容
  Object.assign(appState.currentNote, updateData)
  
  // 实时保存到本地
  saveAppData()

  // 如果用户已登录，设置5秒后保存到云端
  if (authState.isLoggedIn && appState.currentNote.syncStatus === 'synced') {
    // 清除之前的定时器
    if (cloudSaveTimer) {
      clearTimeout(cloudSaveTimer)
    }
    
    // 设置新的5秒定时器
    cloudSaveTimer = setTimeout(async () => {
      if (appState.currentNote) {
        try {
          const updated = await NoteAPI.update(appState.currentNote.id, {
            title: appState.currentNote.title,
            content: appState.currentNote.content,
            updatedAt: appState.currentNote.updatedAt
          })
          if (updated) {
            // 更新本地数据
            Object.assign(appState.currentNote, updated)
            saveAppData()
            console.log('笔记已自动保存到云端')
          }
        } catch (error) {
          console.error('云端保存失败:', error)
        }
      }
    }, 5000) // 5秒延迟
  } else if (!authState.isLoggedIn) {
    // 用户未登录，标记为待同步
    appState.currentNote.syncStatus = 'pending'
    saveAppData()
  }
}

// 监听应用状态变化，自动保存数据
watch(
  () => [appState.folders, appState.notes, appState.currentFolder, appState.currentNote],
  () => {
    saveAppData()
  },
  { deep: true }
)

// 存储使用情况
const storageUsage = ref({ used: 0, available: 0 })

/**
 * 获取存储使用情况
 */
const updateStorageUsage = async (): Promise<void> => {
  try {
    storageUsage.value = await getStorageUsage()
  } catch (error) {
    console.error('获取存储使用情况失败:', error)
  }
}

// 定期更新存储使用情况
setInterval(updateStorageUsage, 30000) // 每30秒更新一次

/**
 * 处理数据导入
 * @param data 导入的数据
 */
const handleDataImported = (data: AppData): void => {
  appState.folders = data.folders
  appState.notes = data.notes
  appState.currentFolder = data.currentFolder

  // 恢复当前选中的笔记
  if (data.currentNoteId) {
    appState.currentNote = appState.notes.find((note) => note.id === data.currentNoteId) || null
  } else {
    appState.currentNote = null
  }

  updateFolderCounts()
  showSettings.value = false
}

/**
 * 创建共享笔记
 * @param noteData 笔记数据
 * @param folderId 文件夹ID
 */
const createSharedNote = (noteData: any, folderId: number): void => {
  // 找到对应的文件夹
  const targetFolder = appState.folders.find(f => f.name === `${noteData.title.split(' ')[0]} (共享)` || f.id === folderId)
  if (!targetFolder) {
    console.error('找不到目标文件夹')
    return
  }
  
  const newNote: Note = {
    id: Date.now() + Math.random(),
    title: noteData.title,
    content: noteData.content,
    folderId: targetFolder.id,
    createdAt: noteData.createdAt || formatDateTime(),
    updatedAt: noteData.updatedAt || formatDateTime(),
    syncStatus: 'local'
  }
  
  appState.notes.push(newNote)
  updateFolderCounts()
  saveAppData()
  
  console.log('共享笔记创建成功:', newNote.title)
}

/**
 * 获取当前应用数据
 */
const getCurrentAppData = (): AppData => {
  return {
    folders: appState.folders,
    notes: appState.notes,
    currentFolder: appState.currentFolder,
    currentNoteId: appState.currentNote?.id || null
  }
}
</script>

<template>
  <div class="note-app">
    <!-- 左侧：文件夹列表 -->
    <FolderList
      :folders="appState.folders"
      :current-folder="appState.currentFolder"
      @folder-select="handleFolderSelect"
      @create-folder="(name, parentId, isShared) => createFolder(name, parentId, isShared)"
      @rename-folder="renameFolder"
      @delete-folder="deleteFolder"
      @move-folder="moveFolder"
      @reorder-folders="reorderFolders"
      @update-folder="updateFolder"
      @move-note-to-folder="moveNoteToFolder"
      @create-shared-note="createSharedNote"
      @show-settings="showSettings = true"
    />

    <!-- 中间：笔记列表 -->
    <NoteList
      :notes="appState.notes"
      :folders="appState.folders"
      :current-folder="appState.currentFolder"
      :current-note="appState.currentNote"
      @note-select="handleNoteSelect"
      @create-note="createNewNote"
      @rename-note="renameNote"
      @delete-note="deleteNote"
      @move-note-to-folder="moveNoteToFolder"
    />

    <!-- 右侧：主内容区 -->
    <div class="main-content">
      <!-- 笔记编辑器 -->
      <div class="editor-container">
        <NoteEditor
          :note="appState.currentNote"
          @update-note="handleNoteUpdate"
        />
      </div>
    </div>

    <!-- 设置面板 -->
    <Settings
      v-if="showSettings"
      :app-data="getCurrentAppData()"
      @data-imported="handleDataImported"
      @close="showSettings = false"
    />

    <!-- 通知容器 -->
    <NotificationContainer />
  </div>
</template>
